<template>
  <div class="rich-text-editor">
    <Toolbar
        style="border-bottom: 1px solid #ccc"
        :editor="editorRef"
        :defaultConfig="toolbarConfig"
        :mode="mode"
    />
    <Editor
        style="height: 500px; overflow-y: hidden;"
        v-model="text"
        :defaultConfig="editorConfig"
        :mode="mode"
        @onCreated="handleCreated"
    />
  </div>
</template>

<script setup>
import {onBeforeUnmount, ref, shallowRef} from 'vue'
import '@wangeditor/editor/dist/css/style.css'
import {Editor, Toolbar} from '@wangeditor/editor-for-vue'
import {ElMessage} from "element-plus";
import {baseURL} from "@/request/request.js";
import {checkFile, uploadChunkList} from "@/api/file.js";
import {getChunkList, getHash} from "@/common/utils/utils.js";

// 编辑器实例，必须用 shallowRef
const editorRef = shallowRef()
// 模式
const mode = ref('default') // 或 'simple'

// 工具栏配置
const toolbarConfig = {
  excludeKeys: []
}

const customUpload = async (file, insertFn) => {
  //分片尺寸
  const chuckSize = 1024 * 1024 * 5;
  //文件上传
  if (!file) {
    return
  }
  if (!file.type.includes('image')) {
    ElMessage({
      type: 'error',
      message: '文件格式错误，请上传图片类型',
    })
    return;
  }
  //判断文件后缀
  if (!file.name.includes('.')) {
    ElMessage({
      type: 'error',
      message: '文件格式错误',
    })
  }
  const chunkList = getChunkList(file, chuckSize);
  const md5 = await getHash(chunkList)
  const {data} = await checkFile(md5)

  if (data.url) {
    insertFn(baseURL + data.url)
    return
  }

  if (data.index) {
    await uploadChunk(file, chunkList, md5, data.index, insertFn)
    return
  }

  await uploadChunk(file, chunkList, md5,0, insertFn)
}
//分片上传
const uploadChunk = async (file, chunkList, md5, index, insertFn) => {
  const fileName = file.name
  const fileType = file.type
  const size = file.size
  for (index; index < chunkList.length; index++) {
    const formData = new FormData()
    formData.append('file', chunkList[index])
    formData.append('fileName', fileName)
    formData.append('fileType', fileType)
    formData.append('index', index)
    formData.append('size', size)
    formData.append('md5', md5)
    formData.append('total', chunkList.length)
    const {code, data, msg} = await uploadChunkList(formData)
    if (code === 200) {
      insertFn(baseURL + data.url)
    } else if (code === 400) {
      ElMessage.error(msg)
    }
  }
}

// 编辑器配置
const editorConfig = {
  placeholder: '请输入内容...',
  MENU_CONF: {
    // 图片上传配置
    uploadImage: {
      // 自定义图片上传逻辑
      customUpload
    },
    // 链接配置
    insertLink: {
      checkLink: (url) => {
        // 可以在这里自定义链接校验逻辑
        return true
      },
      parseLinkUrl: (url) => {
        // 可以在这里自定义链接解析逻辑
        return url
      }
    }
  }
}

// 组件销毁时，也及时销毁编辑器
onBeforeUnmount(() => {
  const editor = editorRef.value
  if (editor == null) return
  editor.destroy()
})

// 编辑器回调函数
const handleCreated = (editor) => {
  editorRef.value = editor // 记录 editor 实例
}

// 内容 HTML
const text = defineModel('text', {type: String, required: true})
</script>

<style scoped>
.rich-text-editor {
  border: 1px solid #ccc;
  z-index: 100;
}

:deep(.w-e-toolbar) {
  border-bottom: 1px solid #ccc;
  padding: 8px;
}

:deep(.w-e-text-container) {
  height: 500px !important;
}
</style>